﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Windows;
using System.IO;
using HalconDotNet;
using GalaSoft.MvvmLight;
using System.Collections;
using ElementLib.Interface;
using ElementLib;
using CommonLib;
using Point = ElementLib.Point;
using Mark = CommonLib.ConstValue.Counter;
namespace Project1.Model
{

    public class CoreModel : ObservableObject
    {

        private HObject ho_Image;
        private Point mousePosition;
        private bool measureMode = false;
        private bool drawMode = false;
        private HTuple hv_Mode = null, Threshold1 = new HTuple(0), Threshold2 = new HTuple(20), hv_Width, hv_Height; 
        private bool isAutoThreshold = false;   //自动阈值是否启用
        private HTuple hv_MinRadius = new HTuple(18), hv_MaxRadius = new HTuple(38);//检测半径的最小和最大值
        public HTuple modelCentreRow, modelCentreColumn;
        private int currentMeasureType = 0;
        private string default_drawShape = ConstValue.DRAW_RECTANGLE1;
        private bool pressed = false;

        private MeasurePlan measurePlan;

        private object image_lock = new object();
        private int invalidPointsNum = 0;
        private bool isAutoEdgeScope;
        public HTuple windowHandle = null;
        private HTuple hv_ModelID = null;
        private HObject modelImage = null;
        private List<HTuple> drawing_objects;

       // private List<IElem> points;
        //private List<IElem> circles;
        //private List<IElem> lines;
        private List<double> distances;
        private List<double> angles;
        //private List<ROI> interactROIs;

        private List<CirclePack> circlePacks;
        private List<PointPack> pointPacks;
        private List<LinePack> linePacks;

        private List<IComplexMes> icms; //存储二元计划
        private List<IElemPack> ieps;  //存储当前选中的元素

        private List<SupportLine> supportLines;
        private SupportLine currentSupportLinePtr;
        private HObject tempContours;
        private Point currentStartPoint;
        private Point currentEndPoint;
        //private Point prior_p1;
        // private Point prior_p2;

        private string elemInfo;

        private CirclePack currenCirclePack = null;
        private LinePack currentLinePack = null;
        private PointPack currentPointPack = null;
        private string currentDrawMode = "";
        private CC currentCC = null;
        private LC currentLC = null;
        private LL currentLL = null;
        private PP currentPP = null;
        private PL currentPL = null;
        private int[] countList = new int[30];

        private int maxROInum = 1; 

        private List<HObject> saved_ROI_Contours;
        private string itemName;
        private string tips;
        private string peakPointMode;
        Action action;
        public delegate void UpdateElementInfo(string mode, Output pe = null);
        public delegate void UpdatePlanInfo();
        private UpdateElementInfo updateMethod;
        private UpdatePlanInfo updatePlanMethod;

        public string ELEMINFO { get { return elemInfo; } set { elemInfo = value; RaisePropertyChanged(() => ELEMINFO); } }
        public bool Pressed { get { return pressed; } set { pressed = value; } }

        public int MaxROINum
        {
            get { return maxROInum; }
            set { maxROInum = value; RaisePropertyChanged(() => MaxROINum); }
        }
        public void AddSupline(SupportLine supportLine)
        {
            supportLines.Add(supportLine);
        }
       
        public void AddToList(IElemPack elemPack,int aimlist)
        {
            if (aimlist == ConstValue.CIRCLE) circlePacks.Add(new CirclePack((CirclePack)elemPack));
            else if (aimlist == ConstValue.POINT) pointPacks.Add(new PointPack((PointPack)elemPack));
            else if (aimlist == ConstValue.LINE) linePacks.Add(new LinePack((LinePack)elemPack));
            else if (aimlist == ConstValue.SUPLINE) supportLines.Add(new SupportLine((SupportLine)elemPack));
        }
        public IElemPack FindMethod(string name, int aimlist)
        {
            IElemPack rs = null;
            if (aimlist == ConstValue.CIRCLE)
            {
                foreach (var item in circlePacks)
                {
                    if (name == item.Name)
                    {
                        rs = item;
                    }
                }
            } else if (aimlist == ConstValue.POINT)
            {
                foreach (var item in pointPacks)
                {
                    if (name == item.Name)
                    {
                        rs = item;
                    }
                }
            } else if (aimlist == ConstValue.LINE)
            {
                foreach (var item in linePacks)
                {
                    if (name == item.Name)
                    {
                        rs = item;
                    }
                }
            }
            return rs;
        }

        public CoreModel(HTuple window)
        {
            InitParams(window);
        }

        public CoreModel()
        {
            InitParams();
        }

        public string Tips
        {
            get { return tips; }
            set { tips = value; RaisePropertyChanged(() => Tips); }
        }
        public void InitParams(HTuple window = null)
        {
            measurePlan = new MeasurePlan();
            supportLines = new List<SupportLine>();
            ieps = new List<IElemPack>();
            windowHandle = window;
            circlePacks = new List<CirclePack>();
            pointPacks = new List<PointPack>();
            linePacks = new List<LinePack>();
            icms = new List<IComplexMes>();
            drawing_objects = new List<HTuple>();
            //points = new List<IElem>();
            //circles = new List<IElem>();
            //lines = new List<IElem>();
            distances = new List<double>();
            angles = new List<double>();
            saved_ROI_Contours = new List<HObject>();
            //interactROIs = new List<ROI>();
            LoadConfigFile(@"D:\Documents\Desktop\test");
        }

        public void LoadConfigFile(string path)
        {

        }
        public void SetUpdateFunc(UpdateElementInfo method)
        {
            updateMethod = method;
        }
        public void SetUpdateFunc(UpdatePlanInfo method)
        {
            updatePlanMethod = method;
        }
        
        public void SetCallBackAction(Action action)
        {
            this.action = action;
        }

        public void Save_MeasurePlan(string path = ConstValue.DEFAULT_MEASUREPLAN_PATH)
        {
            //string path = @"D:\Documents\Desktop\test"
            Apply("update");
            measurePlan.SaveToLocal(path);
            updatePlanMethod();
            //MeasurePlan.LoadMeasure(path);
        }
        public void callBack()
        {
            if (currenCirclePack != null)
            {
                currenCirclePack.Dispose();
                currenCirclePack = null;
            }
            if (currentPointPack != null)
            {
                currentPointPack.Dispose();
                currentPointPack = null;
            }
            if (currentLinePack != null)
            {
                currentLinePack.Dispose();
                currentLinePack = null;
            }
            action.Invoke();
            SetMeasureMode(false);
            SetDrawMode(false);
        }


        public void Execute()
        {
            foreach (var icm in icms)
            {
                icm.Execute(FindMethod);
            }
         
        }
        public string PeakPointMode
        {
            get
            {
                return peakPointMode;
            }
            set
            {
                peakPointMode = value;
                RaisePropertyChanged(() => PeakPointMode);
            }
        }

        public List<double> Distances
        {
            get { return distances; }
        }

        public List<double> Angles
        {
            get { return angles; }
        }
        public List<PointPack> Points
        {
            get { return pointPacks; }
        }
        public List<CirclePack> Circle
        {
            get { return circlePacks; }
        }
        public List<LinePack> Lines
        {
            get { return linePacks; }
        }

        public HTuple ModelID
        {
            get { return hv_ModelID; }
        }
        public int InvalidPointsNum
        {
            get
            {
                return invalidPointsNum;
            }
            set
            {
                invalidPointsNum = value;
                RaisePropertyChanged(() => InvalidPointsNum);
            }
        }

        public bool IsAutoEdgeScope
        {
            get
            {
                return isAutoEdgeScope;
            }
            set
            {
                isAutoEdgeScope = value;
                if (isAutoEdgeScope)
                {
                    MessageBox.Show("激活");
                }

                RaisePropertyChanged(() => IsAutoEdgeScope);
            }
        }
        public double minThreshold
        {
            get
            {
                return (double)Threshold1;
            }
            set
            {
                Threshold1 = new HTuple(value);
                RaisePropertyChanged(() => minThreshold);
            }
        }

        public bool IsAutoThreshold
        {
            get
            {
                return isAutoThreshold;
            }
            set
            {
                isAutoThreshold = value;
                RaisePropertyChanged(() => IsAutoThreshold);
            }
        }
        public string ItemName
        {
            get
            {
                return itemName;
            }

            set
            {
                itemName = value;
                Console.WriteLine();
                RaisePropertyChanged(() => ItemName);
            }
        }
        public double maxThreshold
        {
            get
            {
                return (double)Threshold2;
            }
            set
            {
                Threshold2 = new HTuple(value);
                RaisePropertyChanged(() => maxThreshold);
            }
        }

        public double minRadius
        {
            get
            {
                return (double)hv_MinRadius;
            }
            set
            {
                hv_MinRadius = new HTuple(value);
                RaisePropertyChanged(() => minRadius);
            }
        }

        public double maxRadius
        {
            get
            {
                return (double)hv_MaxRadius;
            }
            set
            {
                hv_MaxRadius = new HTuple(value);
                RaisePropertyChanged(() => maxRadius);
            }
        }

        public void Execute(IComplexMes icm)
        {

        }

        public bool CheckIfWindowLoaded()
        {
            if (windowHandle == null) return false;
            return true;
        }

        public void ApplySupLineChange()
        {
            if (pressed == false) return;
            pressed = false;
            if (tempContours == null || currentStartPoint == null || currentEndPoint == null) return;
            currentSupportLinePtr.UpdateCurrentInfo(tempContours, currentStartPoint, currentEndPoint);
            HOperatorSet.SetColor(windowHandle, "green");
            HOperatorSet.DispObj(currentSupportLinePtr.LineContours, windowHandle);
           //MessageBox.Show("松开");
        }

        public void SetWindowHandle(HTuple windowHandle)
        {
          
            this.windowHandle = new HTuple(windowHandle);
        
            Utils.hv_ExpDefaultWinHandle = this.windowHandle;
        }
        /// <summary>
        /// 模板的注册
        /// </summary>
        public void RegistModel()
        {
            if (hv_ModelID == null)
            {
                MessageBox.Show("不存在已经提取的模板", "错误", MessageBoxButton.OK);
                return;
            }
            Utils.Save_model(hv_ModelID, ho_Image, modelImage);
        }
        public void addDrawingObject(HTuple obj)
        {
            drawing_objects.Add(new HTuple(obj));
        }

        /// <summary>
        /// 进入测量页面选取元素时调用此方法，首先检查是否进入测量状态，是否完成ROI区域调整
        /// </summary>
        public void FindROI()
        {
            if (measureMode == false) return;
            if (drawMode == true)
            {
                DrawObject(currentDrawMode);
                SetDrawMode(false);
                return;
            }
            bool flag = false;
            HTuple row, column, button;
            try
            {
                HOperatorSet.GetMposition(windowHandle, out row, out column, out button);
                if (supportLines.Count > 0)
                {
                    for (int i = 0; i < supportLines.Count; i++)
                    {
                        HTuple index = null;
                        HOperatorSet.GetRegionIndex(supportLines[i].Region(), row, column, out index);
                        if (index != null && index.TupleLength() == 1)
                        {
                            pressed = true;
                            currentSupportLinePtr = supportLines[i];
                            currentSupportLinePtr.BeTouched(windowHandle, SetSelectedItem);
                            flag = true;
                            break;
                        }
                    }
                }
                if (flag == true) return;
                if (pointPacks.Count > 0)
                {
                    for (int i = 0; i < pointPacks.Count; i++)
                    {
                        HTuple index = null;
                        HOperatorSet.GetRegionIndex(pointPacks[i].Region(), row, column, out index);
                        if (index != null && index.TupleLength() == 1)
                        {
                            pointPacks[i].BeTouched(windowHandle, SetSelectedItem);
                            flag = true;
                            break;
                        }
                    }
                }
                if (flag == true) return;
                if (linePacks.Count > 0)
                {
                    for (int i = 0; i < linePacks.Count; i++)
                    {
                        HTuple index = null;
                        HOperatorSet.GetRegionIndex(linePacks[i].Region(), row, column, out index);
                        if (index != null && index.TupleLength() == 1)
                        {

                            linePacks[i].BeTouched(windowHandle, SetSelectedItem);
                        }
                    }

                }
                if (flag == true) return;
                if (circlePacks.Count > 0)
                {
                    for (int i = 0; i < circlePacks.Count; i++)
                    {
                        HTuple index = null;
                        // HOperatorSet.DispObj(circlePacks[i].Region(), windowHandle);
                        HOperatorSet.GetRegionIndex(circlePacks[i].Region(), row, column, out index);

                        if (index != null && index.TupleLength() == 1)
                        {
                            circlePacks[i].BeTouched(windowHandle, SetSelectedItem);
                        }
                    }
                }

            }
            catch (Exception)
            {

            }






            //MessageBox.Show("没找到");

        }

        public void SetMeasurePlan(MeasurePlan measurePlan)
        {
            ReinitArgs();
            DispElement();
            if (measurePlan == null) throw new Exception();
            this.measurePlan = measurePlan;
            Matching();
            //MessageBox.Show("计划加载成功", "提示", MessageBoxButton.OK);
        }
        public void ShowCurrentPlans()
        {
            StringBuilder head = new StringBuilder();
            foreach (var item in linePacks)
            {
                head.Append(item.Name + "\r\n");
            }

            foreach (var item in circlePacks)
            {
                head.Append(item.Name + "\r\n");
            }
            foreach (var item in pointPacks)
            {
                head.Append(item.Name + "\r\n");
            }
            foreach (var item in icms)
            {
                head.Append(item.Name + "\r\n");
            }
            ELEMINFO = head.ToString();
        }

        public void DispElement()
        {
  
                foreach (var item in pointPacks)
                {
                     item.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                }

                foreach (var item in linePacks)
                {
                  item.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                }

                foreach (var item in circlePacks)
                {
                  item.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                }

                foreach (var item in supportLines)
                {
                    if (item == currentSupportLinePtr)
                    {
                        continue;
                    }
                    item.DispROI(windowHandle);
                }

        }



        public void InitDrawInfo(HTuple drawID)
        {
           // SetCall(CallBack);
            HOperatorSet.SetDrawingObjectParams(drawID, "color", "blue");
            HOperatorSet.SetDrawingObjectParams(drawID, "line_width", 1);
           // HOperatorSet.SetDrawingObjectCallback(drawID, "", );
                   
        }

        public void SetSelectedItem(string itemName,string mode,IElemPack iep = null)
        {
            if(mode == "remove")
            {
                for (int i = 0; i < ieps.Count; i++)
                {
                    if (ieps[i].Name == itemName)
                    {
                        ieps.RemoveAt(i);
                        MessageBox.Show("取消选中");
                        break;
                    }
                }
            }
            else if(mode == "add")
            {
                MessageBox.Show("选中");
                ieps.Add(iep);
            }
        
        }


        public void SetSelectedItem(string mode, SupportLine line = null)
        {
            if (mode == "remove")
            {
                for (int i = 0; i < supportLines.Count; i++)
                {
                    if (supportLines[i] == line)
                    {
                        supportLines.RemoveAt(i);
                        MessageBox.Show("取消选中");
                        break;
                    }
                }
            }
            else if (mode == "add")
            {
                supportLines.Add(line);
            }

        }


        public void DrawObject(string msg)
        {
            if(drawing_objects.Count >= maxROInum)
            {
                return;
            }
            HTuple hv_DrawID= null;
            int defaultLen = 30; 
            int defaultLen2 = 50;
            int defaultRadius = 50;
            int defaultRadius2 = 30;
            HTuple mRow,mColumn,mButton;

            try
            {
                HOperatorSet.GetMposition(windowHandle, out mRow, out mColumn, out mButton);
                if (msg == ConstValue.DRAW_RECTANGLE1) HOperatorSet.CreateDrawingObjectRectangle1(mRow - defaultLen, mColumn - defaultLen, mRow + defaultLen, mColumn + defaultLen, out hv_DrawID);
                else if (msg == ConstValue.DRAW_CIRCLE) HOperatorSet.CreateDrawingObjectCircle(mRow, mColumn, defaultRadius, out hv_DrawID);
                else if (msg == ConstValue.DRAW_RECTANGLE2) HOperatorSet.CreateDrawingObjectRectangle2(mRow, mColumn, 0, defaultLen, defaultLen2, out hv_DrawID);
                else if (msg == ConstValue.DRAW_ELLIPSE) HOperatorSet.CreateDrawingObjectEllipse(mRow, mColumn, 0, defaultRadius, defaultRadius2, out hv_DrawID);
                else if (msg == ConstValue.DRAW_LINE) HOperatorSet.CreateDrawingObjectLine(mRow, mColumn - defaultLen, mRow, mColumn + defaultLen, out hv_DrawID);
                InitDrawInfo(hv_DrawID);
                HOperatorSet.AttachDrawingObjectToWindow(windowHandle, hv_DrawID);
                drawing_objects.Add(new HTuple(hv_DrawID));
            }
            catch(Exception )
            {
                //MessageBox.Show("出错了!");
            }
          

            return;
        }
        

        
        public void ExtendDetect()
        {
            LL ll;
            LC lc;
            CC cc;
            PP pp;
            PL pl;
            Output output = null;
            switch (currentMeasureType)
            {
                case ConstValue.MEASURE_LL_ANGLE:
                    ItemName = "线线角度" + countList[(int)Mark.线线角度]++;
                    ll = new LL() { Type = ConstValue.MEASURE_LL_ANGLE};
                    if (ll.loadElem(ieps))
                    {
                        output = ll.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentLL = ll;
                    }
                    break;
                case ConstValue.MEASURE_LL_Concate:
                    ItemName = "线线拼接" + countList[(int)Mark.线线拼接]++;
                    ll = new LL() { Type = ConstValue.MEASURE_LL_Concate };
                    
                    if (ll.loadElem(ieps))
                    {
                        output = ll.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentLL = ll;
                    }
                    break;
                case ConstValue.MEASURE_LL_Cross:
                    ItemName = "线线交点" + countList[(int)Mark.线线交点]++;
                    ll = new LL() { Type = ConstValue.MEASURE_LL_Cross };
                    if (ll.loadElem(ieps))
                    {
                        output = ll.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentLL = ll;
                    }
                    break;
                case ConstValue.MEASURE_LL_Dist:
                    ItemName = "线线距离" + countList[(int)Mark.线线距离]++;
                    ll = new LL() { Type = ConstValue.MEASURE_LL_Dist };
                    if (ll.loadElem(ieps))
                    {
                        output = ll.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentSupportLinePtr = ll.SupportLine;
                        currentSupportLinePtr.SetValue(ll.Rs.Dists.First());
                        currentLL = ll;
                    }
                    currentSupportLinePtr.DispLine(windowHandle);
                    currentSupportLinePtr.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                    currentSupportLinePtr.IsSelected = true;
                    supportLines.Add(currentSupportLinePtr);
                    break;
                case ConstValue.MEASURE_LL_InnerC:
                    ItemName = "线线内切圆" + countList[(int)Mark.线线内切圆]++;
                    ll = new LL() { Type = ConstValue.MEASURE_LL_InnerC };
                    if (ll.loadElem(ieps))
                    {
                        output = ll.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentLL = ll;
                    }
                    break;
                case ConstValue.MEASURE_LL_Mid:
                    ItemName = "线线中线" + countList[(int)Mark.线线中线]++;
                    ll = new LL() { Type = ConstValue.MEASURE_LL_Mid };
                    if (ll.loadElem(ieps))
                    {
                        output = ll.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentLL = ll;
                    }                
                    break;
                case ConstValue.MEASURE_PL_DIST:
                    ItemName = "点线距离" + countList[(int)Mark.点线距离]++;
                    pl = new PL() { Type = ConstValue.MEASURE_PL_DIST };
                    if (pl.loadElem(ieps))
                    {
                        output = pl.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentSupportLinePtr = pl.SupportLine;
                        currentSupportLinePtr.SetValue(pl.Rs.Dists.First());
                        currentPL = pl;
                    }
                    currentSupportLinePtr.DispLine(windowHandle);
                    currentSupportLinePtr.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                    currentSupportLinePtr.IsSelected = true;
                    supportLines.Add(currentSupportLinePtr);
                    break;
                case ConstValue.MEASURE_PL_Mid:
                    ItemName = "点线中线" + countList[(int)Mark.点线中线]++;
                    pl = new PL() { Type = ConstValue.MEASURE_PL_Mid };
                    
                    if (pl.loadElem(ieps))
                    {
                        output = pl.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentPL = pl;
                    } 
                    break;
                case ConstValue.MEASURE_PL_Parallel:
                    ItemName = "点线平分" + countList[(int)Mark.点线平分]++;
                    pl = new PL() { Type = ConstValue.MEASURE_PL_Parallel };
                    
                    if (pl.loadElem(ieps))
                    {
                        output = pl.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentPL = pl;
                    }
                    break;
                case ConstValue.MEASURE_PL_VERTICAL:
                    ItemName = "点线垂线" + countList[(int)Mark.点线垂线]++;
                    pl = new PL() { Type = ConstValue.MEASURE_PL_VERTICAL };
                    
                    if (pl.loadElem(ieps))
                    {
                        output = pl.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentPL = pl;
                    }
                    break;
                case ConstValue.MEASURE_PP_DIST:
                    ItemName = "点点距离" + countList[(int)Mark.点点距离]++;
                    pp = new PP() { Type = ConstValue.MEASURE_PP_DIST };
                    
                    if (pp.loadElem(ieps))
                    {
                        pp.Execute(FindMethod);
                        currentSupportLinePtr = pp.SupportLine;
                        currentSupportLinePtr.SetValue(pp.Rs.Dists.First());
                        currentPP = pp;
                    }
                   
                    //SetPriorPoints(sek[0].P, pointPacks[1].P);
                    // supportLines.Add(pp.SupportLine);
                   // currentSupportLinePtr.SetLine( prior_p1, prior_p2, prior_p1, prior_p2);
                    currentSupportLinePtr.DispLine(windowHandle);
                    currentSupportLinePtr.DispROI(windowHandle,ConstValue.UNSELECTED_COLOR);
                    currentSupportLinePtr.IsSelected = true;
                    supportLines.Add(currentSupportLinePtr);
                    break;
                case ConstValue.MEASURE_PP_Mid:
                    ItemName = "点点中线" + countList[(int)Mark.点点中线]++;
                    pp = new PP() { Type = ConstValue.MEASURE_PL_DIST };

                   
                    if (pp.loadElem(ieps))
                    {
                        output = pp.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentPP = pp;
                    }
                    break;
                case ConstValue.MEASURE_P_FitLine:
                    ItemName = "点拟合线" + countList[(int)Mark.点拟合线]++;
                    pp = new PP() { Type = ConstValue.MEASURE_P_FitLine };
                    
                    if (pp.loadElem(ieps))
                    {
                        output = pp.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentPP = pp;
                    }
                    break;
                case ConstValue.MEASURE_CC_Cross:
                    ItemName = "圆圆交点" + countList[(int)Mark.圆圆交点]++;
                    cc = new CC() { Type = ConstValue.MEASURE_CC_Cross };
                   
                    if (cc.loadElem(ieps))
                    {
                        output = cc.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentCC = cc;
                    }
                    break;
                case ConstValue.MEASURE_CC_DIST:
                    ItemName = "圆圆距离" + countList[(int)Mark.圆圆距离]++;
                    cc = new CC() { Type = ConstValue.MEASURE_CC_DIST };
                   
                    if (cc.loadElem(ieps))
                    {
                        output = cc.Execute(FindMethod);
                        currentSupportLinePtr = cc.SupportLine;
                        currentSupportLinePtr.SetValue(cc.Rs.Dists.First());
                        currentCC = cc;
                    }
                    break;
                case ConstValue.MEASURE_CC_Mid:
                    ItemName = "圆圆中心圆" + countList[(int)Mark.圆圆中心圆]++;
                    cc = new CC() { Type = ConstValue.MEASURE_CC_Mid };
                    
                    if (cc.loadElem(ieps))
                    {
                        output = cc.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentCC = cc;
                    }
                    break;
                case ConstValue.MEASURE_LC_Cross:
                    ItemName = "线圆交点" + countList[(int)Mark.线圆交点]++;
                    lc = new LC() { Type = ConstValue.MEASURE_LC_Cross };
                    
                    if (lc.loadElem(ieps))
                    {
                        output = lc.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentLC = lc;
                    }
                    break;
                case ConstValue.MEASURE_LC_DIST:
                    ItemName = "线圆距离" + countList[(int)Mark.线圆距离]++;
                    lc = new LC() { Type = ConstValue.MEASURE_LC_DIST };
                   
                    if (lc.loadElem(ieps))
                    {
                        output = lc.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentLC = lc;
                    }
                    //supportLines.Add(lc.SupportLine);
                    break;
                case ConstValue.MEASURE_C_RADIUS:
                    ItemName = "圆径" + countList[(int)Mark.圆径]++;
                    cc = new CC() { Type = ConstValue.MEASURE_C_RADIUS };
                   
                    if (cc.loadElem(ieps))
                    {
                        output = cc.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentCC = cc;
                    }
                    break;
                case ConstValue.MEASURE_C_Center:
                    ItemName = "圆心" + countList[(int)Mark.圆心]++;
                    cc = new CC() { Type = ConstValue.MEASURE_C_Center };
                  
                    if (cc.loadElem(ieps))
                    {
                        output = cc.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentCC = cc;
                    }
                    break;
                case ConstValue.MEASURE_Arc_Concat:
                    ItemName = "圆弧拼接" + countList[(int)Mark.圆弧拼接]++;
                    cc = new CC() { Type = ConstValue.MEASURE_Arc_Concat };
                  
                    if (cc.loadElem(ieps))
                    {
                        output = cc.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentCC = cc;
                    }
                    break;
                case ConstValue.MEASURE_ARC_ANGLE:
                    ItemName = "圆弧角度" + countList[(int)Mark.圆弧角度]++;
                    cc = new CC() { Type = ConstValue.MEASURE_ARC_ANGLE };
                   
                    if (cc.loadElem(ieps))
                    {
                        output = cc.Execute(FindMethod);
                        output.DispROI(windowHandle);
                        currentCC = cc;
                    }
                    break;
            }
            if (output != null) DecompOutput(output);
        }


        public void MoveSupportLine()
        {
            if (currentSupportLinePtr == null) return;
            try
            {


                currentSupportLinePtr.Moving(windowHandle, out tempContours, out currentStartPoint, out currentEndPoint);
                HOperatorSet.ClearWindow(windowHandle);
                //MessageBox.Show("11");
                currentSupportLinePtr.SetCurrentPpoint( currentStartPoint, currentEndPoint);
                currentSupportLinePtr.DispLine(windowHandle);
                HOperatorSet.DispObj(tempContours, windowHandle);
                DispElement();
            }
            catch (Exception)
            {

            }
       
        }

        public void DecompOutput(Output output)
        {
            if (output.Type == ConstValue.LINE)
            {
                foreach (var item in output.Ls())
                {
                    item.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                    //this.lines.Add(new Line(item));
                    //this.linePacks.Add();
                    currentLinePack = new LinePack() { L = new Line(item) };
                }
            }
            else if (output.Type == ConstValue.CIRCLE)
            {
                foreach (var item in output.Cs())
                {
                    item.dispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                    //this.circles.Add(new Circle(item));
                    //this.circlePacks.Add(new CirclePack() { C = new Circle(item)});
                    currenCirclePack = new CirclePack() { C = new Circle(item) };
                }
            }
            else if (output.Type == ConstValue.POINT)
            {
                foreach (var item in output.Ps())
                {
                    item.dispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                    //this.points.Add(new Point(item));
                    //this.pointPacks.Add(new PointPack() { P = new Point(item) });
                    currentPointPack = new PointPack() { P = new Point(item) };
                }
            }
        }

        public void ReinitArgs()
        {
            circlePacks.Clear();
            linePacks.Clear();
            pointPacks.Clear();
            //lines.Clear();
            //circles.Clear();
            //points.Clear();
            distances.Clear();
            supportLines.Clear();
            angles.Clear();
        }

      
        public void Matching()
        {
           
            if(Utils.hv_ExpDefaultWinHandle==null) Utils.hv_ExpDefaultWinHandle = windowHandle;
            ReinitArgs();
            updateMethod(ConstValue.EMPTY_ELEMLIST);
            HTuple homMat2D, reverseHomMat2D, hv_Row, hv_Column, hv_Angle, hv_Score;
            if (hv_ModelID == null)
            {
                var result = MessageBox.Show("模板没有加载", "提示", MessageBoxButton.OK);
                return;
            }
            HOperatorSet.FindShapeModel(ho_Image, hv_ModelID, (new HTuple(0)).TupleRad(),
             (new HTuple(360)).TupleRad(), 0.5, 1, 0.5, "least_squares",
             (new HTuple(6)).TupleConcat(1), 0.75, out hv_Row, out hv_Column, out hv_Angle, out hv_Score);
            HOperatorSet.VectorAngleToRigid(Utils.modelCentreRow, Utils.modelCentreColumn, 0, hv_Row, hv_Column, hv_Angle, out homMat2D);
            HOperatorSet.VectorAngleToRigid(hv_Row,hv_Column , hv_Angle, Utils.modelCentreRow, Utils.modelCentreColumn, 0, out reverseHomMat2D);
            for (int i = 0; i < hv_Score.TupleLength(); i++)
            {
                MessageBox.Show(""+i);
                measurePlan.Execute(ho_Image, homMat2D, reverseHomMat2D, AddToList, AddSupline, FindMethod);
        
                DispElement();
                MessageBox.Show("WellDone", "通知", MessageBoxButton.OK);
            }
          

            //foreach (var plan in plans)
            //{
            //    string planType =   plan.getPlanType();

            //    PlanElement pe = plan.Execute(ho_Image, homMat2D);
            //    if (pe == null)
            //    {
            //        MessageBox.Show("NG", "次品", MessageBoxButton.OK);
            //        return;
            //    }
            //    updateMethod(ConstValue.UPDATE_ELEMLIST,pe);
            //    if (pe.Type == ConstValue.CIRCLE)
            //    {
            //        circles.Add(new Circle(pe.C));
            //    }
            //    else if (pe.Type == ConstValue.LINE)
            //    {
            //        lines.Add(new Line(pe.L));
            //    }
            //    else if (pe.Type == ConstValue.POINT)
            //    {
            //        foreach (var point in pe.Ps)
            //        {
            //            points.Add(new Point(point));
            //        }   
            //    }
            //    else if (pe.Type == ConstValue.DISTANCE)
            //    {
            //        foreach (var dist in pe.Distances)
            //        {
            //            distances.Add(dist);
            //        }

            //    }
            //    else if(pe.Type == ConstValue.ANGLE)
            //    {
            //        angles.Add(pe.A);
            //    }

            //    else
            //    {
            //        MessageBox.Show("异常", "警告", MessageBoxButton.OK);
            //        return;
            //    }
            //}
         
        }


        public void OpenImage()
        {
            ReinitArgs();
            HOperatorSet.ClearWindow(windowHandle);
            var fileName = Utils.Get_path(ConstValue.IMG,false);
            if (fileName != "")
            {
                HOperatorSet.GenEmptyObj(out ho_Image);
                ho_Image.Dispose();
                HOperatorSet.ReadImage(out ho_Image, fileName);
                HOperatorSet.Rgb1ToGray(ho_Image, out ho_Image);
                HOperatorSet.GetImageSize(ho_Image, out hv_Width, out hv_Height);
                //HOperatorSet.SetPart(windowHandle, 0, 0, hv_Height - 1, hv_Width - 1);
                HOperatorSet.AttachBackgroundToWindow(ho_Image, windowHandle);
               // HOperatorSet.DispObj(ho_Image, windowHandle);
                HOperatorSet.GetImageSize(ho_Image, out hv_Width, out hv_Height);
              
             

            }
        }

        public void AdaptWindow()
        {
            if (windowHandle == null) return;
            HOperatorSet.SetPart(windowHandle, 0.0, 0.0, hv_Height - 1, hv_Width - 1);
            HOperatorSet.ClearWindow(windowHandle);
            HOperatorSet.DispObj(ho_Image, windowHandle);
        }

        public void GetMPosition()
        {
            if (windowHandle == null) return  ;
            HTuple row, column, button;
            try
            {
                HOperatorSet.GetMposition(windowHandle, out row, out column, out button);
                if (this.mousePosition == null) mousePosition = new Point(row, column);
                else
                {
                    mousePosition.Row = row;
                    mousePosition.Column = column;
                }
            }
            catch (Exception)
            {
                
            }
     
        }

        public void SetMeasureMode(bool mark)
        {
            this.measureMode = mark;
        }

        public void SetDrawMode(bool mark)
        {
            this.drawMode = mark;
        }

        public  void ImageZoom( HTuple Zoom, bool use_center = false)
        {
            if (windowHandle == null ||ho_Image ==null|| measureMode ==true) return;
            HTuple Width, Height;
            HOperatorSet.GetImageSize(ho_Image, out Width, out Height);
            HTuple Row = Width / 2, Col = Height / 2, Button;
            HTuple Row0, Column0, Row00, Column00, Ht, Wt, r1, c1, r2, c2;

            if (use_center == false)
            {
                try { HOperatorSet.GetMposition(windowHandle, out Row, out Col, out Button); }
                catch (Exception){ MessageBox.Show("鼠标在界外"); }
            }
            HOperatorSet.GetPart(windowHandle, out Row0, out Column0, out Row00, out Column00);
            Ht = Row00 - Row0;
            Wt = Column00 - Column0;
            if (Ht * Wt < 32000 * 32000 || Zoom == 1.5)//普通版halcon能处理的图像最大尺寸是32K*32K。如果无限缩小原图像，导致显示的图像超出限制，则会造成程序崩溃
            {
                r1 = (Row0 + ((1 - (1.0 / Zoom)) * (Row - Row0)));
                c1 = (Column0 + ((1 - (1.0 / Zoom)) * (Col - Column0)));
                r2 = r1 + (Ht / Zoom);
                c2 = c1 + (Wt / Zoom);
                HOperatorSet.SetPart(windowHandle, r1, c1, r2, c2);
            }
            DispElement();
        }
   

        
        public void ClearAllObjects(bool ifContainOther)
        {
            lock (image_lock)
            {
                foreach (HTuple obj in drawing_objects)
                {
                    HOperatorSet.ClearDrawingObject(obj);
                }
                drawing_objects.Clear();
            }
            if (!ifContainOther)
            {
                HOperatorSet.ClearWindow(this.windowHandle);
            }
            
            //window.ClearWindow();
        }
        public void LoadModel()
        {
            HTuple hv_Score, hv_Column, hv_Angle;
            HTuple hv_RefColumn = new HTuple(), hv_HomMat2D = new HTuple(), hv_Row = new HTuple();

            if (hv_ModelID != null)
            {
                var result = MessageBox.Show("已经打开了一个模板,要重新选择吗", "提示", MessageBoxButton.YesNo);
                if (result == MessageBoxResult.No)
                {
                    return;
                }
            }
            var fileName = Utils.Get_path(ConstValue.MODULE,false);

            if (fileName != "")
            {
                string[] sArray = fileName.Split('.');
                string prefix = sArray.AsQueryable().Last();
                string modelImagePath = fileName.Replace(prefix, "bmp");
                if (!File.Exists(modelImagePath))
                {
                    MessageBox.Show("未能找到模板图片");
                    return;
                }

                HOperatorSet.ReadShapeModel(fileName, out hv_ModelID);

                HOperatorSet.GenEmptyObj(out ho_Image);
                HOperatorSet.ReadImage(out ho_Image, modelImagePath);
                HOperatorSet.GetImageSize(ho_Image, out hv_Width, out hv_Height);
                HOperatorSet.FindShapeModel(ho_Image, hv_ModelID, (new HTuple(0)).TupleRad(),
                    (new HTuple(360)).TupleRad(), 0.5, 1, 0.5, "least_squares",
                    (new HTuple(6)).TupleConcat(1), 0.75, out hv_Row, out hv_Column, out hv_Angle, out hv_Score);
                Utils.modelCentreRow = hv_Row.Clone();
                Utils.modelCentreColumn = hv_Column.Clone();

                //HOperatorSet.SetPart(windowHandle, 0, 0, hv_Height - 1, hv_Width - 1);
                HOperatorSet.AttachBackgroundToWindow(ho_Image, windowHandle);
      


            }
        }

        public void RemoveDrawingObject()
        {
            foreach (var drawing_ID in drawing_objects)
            {
                HOperatorSet.ClearDrawingObject(drawing_ID);
                drawing_objects.Remove(drawing_ID);
                if (drawing_objects.Count == 0) break;
            }

        }

        public void Dispose(SupportLine linePtr)
        {
            if (linePtr != null)
            {
                linePtr.Dispose();
                linePtr = null;
            }
        }
        public void Apply(string mode)
        {
            if(mode == "add")
            {
                currentSupportLinePtr = null;
                if (currentPointPack != null)
                {
                    currentPointPack.ApplyChange();
                    pointPacks.Add(new PointPack(currentPointPack));

                    if (currentPointPack.DetectMethod != 0)
                    {
                        var newIep = new PointPack(currentPointPack);
                        newIep.Unload();
                        measurePlan.Add(newIep);
                    }
                    //points.Add(new Point(currentPointPack.P));
                    
                    MessageBox.Show("新增点计划,当前已有计划" + pointPacks.Count + "个");
                    updateMethod(ConstValue.UPDATE_ELEMLIST, new Output(currentPointPack.P, ConstValue.POINT));
                    currentPointPack.Dispose();
                    currentPointPack = null;
                }
                if (currentLinePack != null)
                {
                    currentLinePack.ApplyChange();
                    linePacks.Add(new LinePack(currentLinePack));
                    if (currentLinePack.DetectMethod != 0)
                    {
                        var newIep = new LinePack(currentLinePack);
                        newIep.Unload();
                        measurePlan.Add(newIep);
                    }

                    MessageBox.Show("新增线计划,当前已有计划" + linePacks.Count + "个");
                    updateMethod(ConstValue.UPDATE_ELEMLIST, new Output(currentLinePack.L, ConstValue.LINE));
                    // interactROIs.Add(new ROI(currentLinePack.Contours, currentLinePack.Region, currentLinePack.DispROI));
                    currentLinePack.Dispose();
                    currentLinePack = null;
                }
                if (currenCirclePack != null)
                {
                    currenCirclePack.ApplyChange(mode);
                    circlePacks.Add(new CirclePack(currenCirclePack));


                    if (currenCirclePack.DetectMethod != 0)
                    {
                        var newIep = new CirclePack(currenCirclePack);
                        newIep.Unload();
                        HTuple row, column, area;
                        HOperatorSet.AreaCenter(newIep.DetectROI.Region(), out area, out row, out column);
                        measurePlan.Add(newIep);
                    }
                    //circles.Add(new Circle(currenCirclePack.C));
                    MessageBox.Show("新增圆计划,当前已有计划" + circlePacks.Count + "个");
                    updateMethod(ConstValue.UPDATE_ELEMLIST, new Output(currenCirclePack.C, ConstValue.CIRCLE));
                    // interactROIs.Add(new ROI(currenCirclePack.Contours, currenCirclePack.Region, currenCirclePack.DispROI));
                    currenCirclePack.Dispose();
                    currenCirclePack = null;
                }

                if (currentCC != null)
                {
                    currentCC.ApplyChange(mode);
                    // icms.Add(new CC(currentCC));
                    var icm = new CC(currentCC);
                    icm.Unload();
                    measurePlan.Add(icm);
                    currentCC = null;
                }
                if (currentLC != null)
                {
                    currentLC.ApplyChange(mode);
                    // icms.Add(new LC(currentLC));
                    var icm = new LC(currentLC);
                    icm.Unload();
                    measurePlan.Add(icm);
                    currentLC = null;
                }
                if (currentLL != null)
                {
                    currentLL.ApplyChange(mode);
                    // icms.Add(new LL(currentLL));
                    var icm = new LL(currentLL);
                    icm.Unload();
                    measurePlan.Add(icm);
                    currentLL = null;
                }
                if (currentPP != null)
                {
                    currentPP.ApplyChange(mode);
                    // icms.Add(new PP(currentPP));

                    var icm = new PP(currentPP);
                    icm.Unload();
                    measurePlan.Add(icm);
                    currentPP = null;
                }
                if (currentPL != null)
                {
                    currentPL.ApplyChange(mode);
                    //   icms.Add(new PL(currentPL));

                    var icm = new PL(currentPL);
                    icm.Unload();
                    measurePlan.Add(icm);
                    currentPL = null;
                }
               
            }
            else if(mode == "update")
            {
                for (int i = 0; i < measurePlan.ICMS.Count; i++)
                {
                    measurePlan.ICMS[i].ApplyChange(mode);
                }
            }
            ShowCurrentPlans();
            DispElement();
        }

    public int  DetectPoint(HTuple hv_Mode)
        {
            if(currentPointPack != null)
            {
                MessageBox.Show("上一个未保存点被抛弃");
                currentPointPack = null;
            }
            this.hv_Mode = hv_Mode;
            HTuple rowStart, rowEnd, colStart, colEnd, Nr, Nc, Dist;
            //HTuple mode = new HTuple("positive");
            HObject region = null;
            HObject xld = Utils.Get_ROI_from_drawingObject(drawing_objects);
            if (xld == null)
            {
                MessageBox.Show("未能检测到ROI区域", "提示", MessageBoxButton.OK);
                return 0;
            }
            //Line line = Utils.get_line_fromROI(ho_Image, ROI, Threshold1, Threshold2);
            //HOperatorSet.DispObj(xld, this.windowHandle);
            HOperatorSet.FitLineContourXld(xld, "regression", -1, 0, 5, 1.5, out rowEnd, out colEnd, out rowStart, out colStart, out Nr, out Nc, out Dist);
            Point point = Utils.Get_point_fromLine(ho_Image,windowHandle, hv_Mode, rowStart, colStart, rowEnd, colEnd);
            if (point == null)
            {
                MessageBox.Show("未能检测到点", "提示", MessageBoxButton.OK);
            }
            else
            {
                    Hashtable args = GenerateHashtable(hv_Mode,Threshold1, Threshold2);
                    HOperatorSet.GenRegionContourXld(xld, out region, "filled");
                    currentPointPack = new PointPack(point,ConstValue.MEASURE_POINT, args, new Line(rowStart,colStart,rowEnd,colEnd));
                    currentPointPack.DispROI(windowHandle,ConstValue.UNSELECTED_COLOR);
                    saved_ROI_Contours.Add(new HObject(region));
            }
            RemoveDrawingObject();
            return 1;
        }


        public Hashtable GenerateHashtableLine(HTuple drawID)
        {

            HTuple row1, row2, column1, column2;
            HOperatorSet.GetDrawingObjectParams(drawID, "row1", out row1);
            HOperatorSet.GetDrawingObjectParams(drawID, "row2", out row2);
            HOperatorSet.GetDrawingObjectParams(drawID, "column1", out column1);
            HOperatorSet.GetDrawingObjectParams(drawID, "column2", out column2);
            Hashtable table = new Hashtable();
            table.Add(ConstValue.LINE_BEGIN_ROW, new HTuple(row1));
            table.Add(ConstValue.LINE_BEGIN_COLUMN, new HTuple(column1));
            table.Add(ConstValue.LINE_END_ROW, new HTuple(row2));
            table.Add(ConstValue.LINE_END_COLUMN, new HTuple(column2));
            return table;
        }


        public Hashtable GenerateHashtableCircle(HTuple drawID)
        {
            HTuple row;
            HTuple column;
            HTuple radius;
            HOperatorSet.GetDrawingObjectParams(drawID, "row", out row);
            HOperatorSet.GetDrawingObjectParams(drawID, "column", out column);
            HOperatorSet.GetDrawingObjectParams(drawID, "radius", out radius);
            Hashtable table = new Hashtable();
            table.Add(ConstValue.CIRCLE_ROW, new HTuple(row));
            table.Add(ConstValue.CIRCLE_COLUMN, new HTuple(column));
            table.Add(ConstValue.CIRCLE_RADIUS, new HTuple(radius));
            return table;
        }
        public Hashtable GenerateHashtableRect2(HTuple drawID)
        {
            HTuple row, column, phi, len1, len2;
            HOperatorSet.GetDrawingObjectParams(drawID, "row", out row);
            HOperatorSet.GetDrawingObjectParams(drawID, "column", out column);
            HOperatorSet.GetDrawingObjectParams(drawID, "phi", out phi);
            HOperatorSet.GetDrawingObjectParams(drawID, "length1", out len1);
            HOperatorSet.GetDrawingObjectParams(drawID, "length2", out len2);
            Hashtable table = new Hashtable();
            table.Add(ConstValue.RECT_ROW, new HTuple(row));
            table.Add(ConstValue.RECT_COLUMN, new HTuple(column));
            table.Add(ConstValue.RECT_PHI, new HTuple(phi));
            table.Add(ConstValue.RECT_LEN1, new HTuple(len1));
            table.Add(ConstValue.RECT_LEN2, new HTuple(len2));
            return table;
        }


        public Hashtable GenerateHashtable(HTuple min_radius, HTuple max_radius, HTuple min_threshold, HTuple max_threshold)
        {
            Hashtable table = new Hashtable();
            table.Add(ConstValue.MIN_RADIUS, new HTuple(min_radius));
            table.Add(ConstValue.MAX_RADIUS, new HTuple(max_radius));
            table.Add(ConstValue.MIN_THRESHOLD, new HTuple(min_threshold));
            table.Add(ConstValue.MAX_THRESHOLD, new HTuple(max_threshold));
            return table;
        }

        public Hashtable GenerateHashtable(HTuple mode, HTuple minThreshold, HTuple maxThreshold)
        {
            Hashtable table = new Hashtable();
            table.Add(ConstValue.MODE, new HTuple(mode));
            table.Add(ConstValue.MIN_THRESHOLD, new HTuple(minThreshold));
            table.Add(ConstValue.MAX_THRESHOLD, new HTuple(maxThreshold));
            return table;
        }

        public Hashtable GenerateHashtable(HTuple min_threshold, HTuple max_threshold)
        {
            Hashtable table = new Hashtable();
            table.Add(ConstValue.MIN_THRESHOLD, new HTuple(min_threshold));
            table.Add(ConstValue.MAX_THRESHOLD, new HTuple(max_threshold));
            return table;
        }


        public int DetectPeakPoint(HTuple hv_Mode)
        {
            if (currentPointPack != null)
            {
                MessageBox.Show("上一个未保存点被抛弃");
                currentPointPack = null;
            }
            HObject roi = Utils.Get_ROI_from_drawingObject(drawing_objects);
            if (roi == null)
            {
                MessageBox.Show("未能检测到ROI区域", "提示", MessageBoxButton.OK);
                return 0;
            }
            Point peakPoint = Utils.Get_peakPoint_fromROI(ho_Image, roi, windowHandle, hv_Mode, Threshold1, Threshold2,ItemName);
            if (peakPoint == null)
            {
                MessageBox.Show("未能检测到峰值点", "提示", MessageBoxButton.OK);
            }
            else
            {
             
                HObject contours = null;
                HOperatorSet.GenContourRegionXld(roi, out contours, new HTuple("border"));

                Hashtable args = GenerateHashtableLine(drawing_objects.First());
                currentPointPack = new PointPack(peakPoint, ConstValue.MEASURE_POINT_PEAK, args,new ROI(roi, args,ConstValue.ROI_RECTANGLE));
                currentPointPack.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                saved_ROI_Contours.Add(new HObject(contours));
          
            }
            RemoveDrawingObject();

            return 1;
        }
        public int DetectLine()
        {

            if (currentLinePack != null)
            {
                MessageBox.Show("上一个未保存线被抛弃");
                currentLinePack = null;
            }
            //输入的灰度阈值范围先设置成0到20

            HObject roi = Utils.Get_ROI_from_drawingObject(drawing_objects);
            if (roi == null)
            {
                MessageBox.Show("未能检测到ROI区域", "提示", MessageBoxButton.OK);
                return 0;
            }
            Line line = Utils.Get_line_fromROI(ho_Image, roi, windowHandle,Threshold1, Threshold2);
            if (line == null)
            {
                MessageBox.Show("未能检测到线", "提示", MessageBoxButton.OK);
            }
            else
            {
                    HObject contours = null;
                    HOperatorSet.GenContourRegionXld(roi, out contours, new HTuple("border"));
                    
                    Hashtable args = GenerateHashtable(Threshold1, Threshold2);
                    Hashtable args2 = GenerateHashtableRect2(drawing_objects.First());
                    currentLinePack  = new LinePack(line, ConstValue.MEASURE_LINE, args, new ROI(roi, args2,ConstValue.ROI_RECTANGLE));
                    currentLinePack.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                    saved_ROI_Contours.Add(new HObject(contours));
            }
            RemoveDrawingObject();
            
            return 1;
        }

        public int DetectCircle()
        {
            if (currenCirclePack != null)
            {
                MessageBox.Show("上一个未保存线被抛弃");
                currenCirclePack.Dispose();
                currenCirclePack = null;
            }
            HObject roi = GetROIFromDrawingObject();
            if (roi == null)
            {
                MessageBox.Show("未能检测到ROI区域", "提示", MessageBoxButton.OK);
                return 0;
            }
            
            //hv_Threshold1 = new HTuple(40), hv_Threshold2 = new HTuple(255)
            Circle rsCircle = Utils.Get_circle_fromROI(ho_Image, roi, windowHandle, hv_MinRadius, hv_MaxRadius, Threshold1, Threshold2);
            //if (rsCircle == null)
            //{
            //    MessageBox.Show("未能检测到圆", "提示", MessageBoxButton.OK);
            //    return 0;
            //}
            if (rsCircle != null)
            {
                    HObject contours = null;
                    HOperatorSet.GenContourRegionXld(roi, out contours, new HTuple("border"));
                    saved_ROI_Contours.Add(contours);
                    Hashtable args = GenerateHashtable(hv_MinRadius, hv_MaxRadius, Threshold1, Threshold2) ;
                    Hashtable args2 = GenerateHashtableCircle(drawing_objects.First());
                    currenCirclePack = new CirclePack(rsCircle, ConstValue.MEASURE_CIRCLE, args,new ROI(roi,args2,ConstValue.ROI_CIRCLE));
                    currenCirclePack.DispROI(windowHandle, ConstValue.UNSELECTED_COLOR);
                    //plans.Add(plan);
            }
            RemoveDrawingObject();
            return 1;
        }
        public  HObject GetROIFromDrawingObject()
        {
            HObject ROI = null;
            if (drawing_objects.Count == 0) return ROI;
            HObject tempROI = null;
            foreach (var drawingID in drawing_objects)
            {

                HOperatorSet.GetDrawingObjectIconic(out tempROI, drawingID);
                if (ROI == null)
                {
                    ROI = tempROI.Clone();
                }
                else
                {
                    HOperatorSet.Union2(ROI, tempROI, out ROI);
                }
                tempROI.Dispose();
            }
            return ROI;
        }

        public void ExtractModel()
        {
            HObject ho_Object, ho_ModelContours,ho_ImageReduced;
            HObject ROI = null;
            HOperatorSet.GenEmptyObj(out ho_ModelContours);
            HOperatorSet.GenEmptyObj(out ho_Object);
            int len = drawing_objects.Count;
            if (len == 0)
            {
                MessageBox.Show("未能检测到ROI区域", "提示", MessageBoxButton.OK);
                return;
            }
            else
            {
                foreach (var drawing_ID in drawing_objects)
                {
                    HOperatorSet.GetDrawingObjectIconic(out ho_Object, drawing_ID);
                    if (ROI == null)
                    {
                        ROI = ho_Object;
                    }
                    else
                    {
                        HOperatorSet.Union2(ROI, ho_Object, out ROI);
                    }
                }
            }

            //ho_ImageReduced.Dispose();
            HOperatorSet.ReduceDomain(ho_Image, ROI, out ho_ImageReduced);
            HOperatorSet.CreateShapeModel(ho_ImageReduced, 5, (new HTuple(0)).TupleRad(),
            (new HTuple(360)).TupleRad(), (new HTuple(0.6174)).TupleRad(),
            (new HTuple("none")).TupleConcat("no_pregeneration"), "use_polarity",
            ((new HTuple(49)).TupleConcat(56)).TupleConcat(22), 10, out hv_ModelID);


            if (hv_ModelID != null)
            {

                Utils.Get_modelImage(ho_Image,windowHandle, out modelImage, hv_ModelID);
                HOperatorSet.DispObj(modelImage,this.windowHandle);
                MessageBox.Show("成功提取模型", "结果", MessageBoxButton.OK);
                HOperatorSet.AttachBackgroundToWindow(modelImage,this.windowHandle);
                ho_Image = modelImage;

            }
            else
            {
                MessageBox.Show("提取失败", "结果", MessageBoxButton.OK);
            }

            RemoveDrawingObject();
        }

        public void GetDefaultName(int type)
        {
            currentMeasureType = type;
         
            switch (type)
            {
                case ConstValue.MEASURE_CIRCLE:
                    ItemName = "圆" + (circlePacks.Count);
                    Tips = ConstValue.CIRCLETIP;
                    currentDrawMode = ConstValue.DRAW_CIRCLE;
                    break;
                case ConstValue.MEASURE_CIRCLE2:
                    ItemName = "峰值圆" + countList[(int)Mark.峰值圆];
                    Tips = ConstValue.CIRCLETIP;
                    currentDrawMode = ConstValue.DRAW_CIRCLE;
                    break;
                case ConstValue.MEASURE_POINT:
                    ItemName = "点" + (pointPacks.Count);
                    Tips = ConstValue.POINTTIP;
                    currentDrawMode = ConstValue.DRAW_LINE;
                    break;
                case ConstValue.MEASURE_POINT_PEAK:
                    ItemName = "峰值点" + countList[(int)Mark.峰值点];
                    Tips = ConstValue.POINTTIP;
                    currentDrawMode = ConstValue.DRAW_RECTANGLE2;
                    break;
                case ConstValue.MEASURE_LINE:
                    ItemName = "线" + (linePacks.Count);
                    Tips = ConstValue.LINETIP;
                    currentDrawMode = ConstValue.DRAW_RECTANGLE2;
                    break;
                case ConstValue.MEASURE_LINE_PEAK:
                    ItemName = "峰值线" + countList[(int)Mark.峰值线];
                    Tips = ConstValue.LINETIP;
                    currentDrawMode = ConstValue.DRAW_RECTANGLE2;
                    break;
                case ConstValue.MEASURE_LL_ANGLE:
                    ItemName = "线线角度" + countList[(int)Mark.线线角度];
                    Tips = ConstValue.LLTIP;
                    break;
                case ConstValue.MEASURE_LL_Concate:
                    ItemName = "线线拼接" + countList[(int)Mark.线线拼接];
                    Tips = ConstValue.LLTIP;
                    break;
                case ConstValue.MEASURE_LL_Cross:
                    ItemName = "线线交点" + countList[(int)Mark.线线交点];
                    Tips = ConstValue.LLTIP;
                    break;
                case ConstValue.MEASURE_LL_Dist:
                    ItemName = "线线距离" + countList[(int)Mark.线线距离];
                    Tips = ConstValue.LLTIP;
                    break;
                case ConstValue.MEASURE_LL_InnerC:
                    ItemName = "线线内切圆" + countList[(int)Mark.线线内切圆];
                    Tips = ConstValue.LLTIP;
                    break;
                case ConstValue.MEASURE_LL_Mid:
                    ItemName = "线线中线" + countList[(int)Mark.线线中线];
                    Tips = ConstValue.LLTIP;
                    break;
                case ConstValue.MEASURE_PL_DIST:
                    ItemName = "点线距离" + countList[(int)Mark.点线距离];
                    Tips = ConstValue.PLTIP;
                    break;
                case ConstValue.MEASURE_PL_Mid:
                    ItemName = "点线中线" + countList[(int)Mark.点线中线];
                    Tips = ConstValue.PLTIP;
                    break;
                case ConstValue.MEASURE_PL_Parallel:
                    ItemName = "点线平分" + countList[(int)Mark.点线平分];
                    Tips = ConstValue.PLTIP;
                    break;
                case ConstValue.MEASURE_PL_VERTICAL:
                    ItemName = "点线垂线" + countList[(int)Mark.点线垂线];
                    Tips = ConstValue.PLTIP;
                    break;
                case ConstValue.MEASURE_PP_DIST:
                    ItemName = "点点距离" + countList[(int)Mark.点点距离];
                    Tips = ConstValue.PPTIP;
                    break;
                case ConstValue.MEASURE_PP_Mid:
                    ItemName = "点点中线" + countList[(int)Mark.点点中线];
                    Tips = ConstValue.PPTIP;
                    break;
                case ConstValue.MEASURE_P_FitLine:
                    ItemName = "点拟合线" + countList[(int)Mark.点拟合线];
                    Tips = ConstValue.PPTIP;
                    break;
                case ConstValue.MEASURE_CC_Cross:
                    ItemName = "圆圆交点" + countList[(int)Mark.圆圆交点];
                    Tips = ConstValue.CCTIP;
                    break;
                case ConstValue.MEASURE_CC_DIST:
                    ItemName = "圆圆距离" + countList[(int)Mark.圆圆距离];
                    Tips = ConstValue.CCTIP;
                    break;
                case ConstValue.MEASURE_CC_Mid:
                    ItemName = "圆圆中心圆" + countList[(int)Mark.圆圆中心圆];
                    Tips = ConstValue.CCTIP;
                    break;
                case ConstValue.MEASURE_LC_Cross:
                    ItemName = "线圆交点" + countList[(int)Mark.线圆交点];
                    Tips = ConstValue.LCTIP;
                    break;
                case ConstValue.MEASURE_LC_DIST:
                    ItemName = "线圆距离" + countList[(int)Mark.线圆距离];
                    Tips = ConstValue.LCTIP;
                    break;
                case ConstValue.MEASURE_C_RADIUS:
                    ItemName = "圆径" + countList[(int)Mark.圆径];
                    Tips = ConstValue.C_RADIUSTIP;
                    break;
                case ConstValue.MEASURE_C_Center:
                    ItemName = "圆心" + countList[(int)Mark.圆心];
                    Tips = ConstValue.C_CENTERTIP;
                    break;
                case ConstValue.MEASURE_Arc_Concat:
                    ItemName = "圆弧拼接" + countList[(int)Mark.圆弧拼接];
                    Tips = ConstValue.C_CENTERTIP;
                    break;
                case ConstValue.MEASURE_ARC_ANGLE:
                    ItemName = "圆弧角度" + countList[(int)Mark.圆弧角度];
                    Tips = ConstValue.C_CENTERTIP;
                    break;
            }

            
        }
    
        public Point Detect_LL_Cross(Line line1,Line line2)
        {
            
            return Utils.Detect_LL_Cross(line1, line2);
        }

        public Point Detect_LC_Cross(Line line,Circle circle)
        {
            return Utils.Detect_LC_Cross(line, circle);
        }

        public Point Detect_CC_Cross(Circle circle1,Circle circle2)
        {
            return Utils.Detect_CC_Cross(circle1, circle2);   
        }

        public Point Detect_C_Center(Circle circle)
        {
            return Utils.Detect_C_Center(circle);
        }

        public Point Detect_P_Mid(Point point1,Point point2)
        {
            return Utils.Detect_P_Mid(point1, point2);
        }
        public Line Detect_LL_Mid(Line line1,Line line2)
        {
            return Utils.Detect_LL_Mid(line1, line2);
        }

        public Line Detect_PL_Mid(Point point,Line line)
        {
            return Utils.Detect_PL_Mid(point, line);
        }

        public Line Detect_PL_VERTICAL(Point point,Line line)
        {
            return Utils.Detect_PL_VERTICAL(point, line);
        }

        public Line Detect_PL_Parallel(Point point,Line line)
        {
            return Utils.Detect_PL_Parallel(point, line);
        }

        public Line Detect_PP_Mid(Point point1 ,Point point2)
        {
            return Utils.Detect_PP_Mid(point1, point2);
        }

        public Line Detect_P_FitLine(List<Point>points)
        {
            return Utils.Detect_P_FitLine(points);
        }

        public Line Detect_LL_Concate(List<Line>lines)
        {
            return Utils.Detect_LL_Concate(lines);
        }

        public Circle Detect_C_Fit(List<Point>points)
        {
            return Utils.Detect_C_Fit(points);
        }

        public Circle Detect_CC_Mid(Circle c1,Circle c2)
        {
            return Utils.Detect_CC_Mid(c1, c2);
        }

        public Circle Detect_C_SUP(Point point,double radius)
        {
            return Utils.Detect_C_SUP(point, radius);
        }

        public Circle Detect_LL_InnerC(List<Line>lines)
        {
            return Utils.Detect_LL_InnerC(lines);
        }

        public Circle Detect_Arc_Concat(List<Line>lines)
        {
            return Utils.Detect_Arc_Concat(lines);
        }


        public double Detect_PP_DIST(Point point1,Point point2)
        {
            return Utils.Detect_PP_DIST(point1, point2);
        }//点点距离
        public HTuple Detect_PL_DIST(Point point,Line line)
        {
            return Utils.Detect_PL_DIST(point, line);
        }//点线距离
        public double Detect_LL_Dist(Line line1,Line line2)
        {
            return Detect_LL_Dist(line1, line2);
        }//线线距离
        public double[] Detect_PC_DIST(Point point,Circle circle)
        {
            return Utils.Detect_PC_DIST(point, circle);
        }//点圆距离
        public double[] Detect_LC_DIST(Line line,Circle circle)
        {
            return Utils.Detect_LC_DIST(line, circle);
        }//线圆距离
        public double[] Detect_CC_DIST(Circle circle1,Circle circle2)
        {
            return Utils.Detect_CC_DIST(circle1, circle2);
        }//圆圆距离
        public double Detect_C_RADIUS(Circle circle)
        {
            return Utils.Detect_C_RADIUS(circle);

        }//圆径
        public double Detect_ARC_ANGLE(Line arc)
        {
            return Utils.Detect_ARC_ANGLE(arc);
        }//弧度
        public double Detect_LL_ANGLE(Line line1, Line line2)
        {
            return Utils.Detect_LL_ANGLE(line1, line2);
        }//线夹角度
    }
}
